/*
 * Systemprogrammierung
 * Multiplayer-Quiz
 *
 * Server
 * 
 * catalog.c: Implementierung der Fragekatalog-Behandlung und Loader-Steuerung
 */

#include <stdlib.h>
#include <string.h>
#include "catalog.h"
#include "common/rfc.h"
#include "user.h"

struct CatalogInfo *oCatalogList = NULL;
char *CatalogDir = NULL;

// Returns the number of catalogs
int catalog_GetCatalogCount() {
	int i = 0;
	struct CatalogInfo *oTemp = oCatalogList;

	while (oTemp != NULL) {
		i++;
		oTemp = oTemp -> ptrNext;
	}
	return i;
}

// Adds a new user to the cataloglist
void catalog_AddNewCatalog(char *sCatalogName) {
	struct CatalogInfo *oNewCatalogInfo = malloc(sizeof(struct CatalogInfo));

	errorPrint("\nKatalog hinzugefuegt: %s | Kataloganzahl: %d", sCatalogName, catalog_GetCatalogCount() + 1);
	oNewCatalogInfo -> sCatalogName = malloc(strlen(sCatalogName) * sizeof(char)+1);
	strcpy(oNewCatalogInfo -> sCatalogName, sCatalogName);
	oNewCatalogInfo -> bIsSelected = 0;

	// insert new element into list at position 0
	oNewCatalogInfo -> ptrNext = oCatalogList;
	oCatalogList = oNewCatalogInfo;
}

struct CatalogInfo* catalog_GetCatalogList() {
	return oCatalogList;
}

void catalog_SetCatalogDir(char *sDir) {
	if (CatalogDir == NULL) { CatalogDir = malloc(256 * sizeof(char)); }
	strcpy(CatalogDir, sDir);
}

char* catalog_GetCatalogDir() {
	return CatalogDir;
}

int catalog_MarkCatalogAsSelected(char *sCatalogName) {
	int i;
	int iCount = catalog_GetCatalogCount();
	int iReturn = 0;
	struct CatalogInfo *oTemp = catalog_GetCatalogList();

	for (i = 0; i < iCount; i++) {
		if (strcmp(sCatalogName, oTemp -> sCatalogName) == 0) {
			oTemp -> bIsSelected = 1;
			iReturn = 1;
		} else {
			oTemp -> bIsSelected = 0;
		}
		oTemp = oTemp -> ptrNext;
	}
	return iReturn;
}

int catalog_SendCatalogsToClient(int iSocket) {
	int i;
	int iCount = catalog_GetCatalogCount();
	int iMessageLen = 0;
	char *sMessage;
	struct CatalogInfo *oTemp = catalog_GetCatalogList();

	sMessage = malloc((128 + (iCount * 32)) * sizeof(char));

	// Create catalog list
	for (i = 0; i < iCount; i++) {
		sMessage[iMessageLen] = (uint8_t)(strlen(oTemp -> sCatalogName) / 256);
		sMessage[iMessageLen + 1] = (uint8_t)strlen(oTemp -> sCatalogName);
		iMessageLen = iMessageLen + 2;
		memmove(sMessage + iMessageLen, oTemp -> sCatalogName, strlen(oTemp -> sCatalogName));
		iMessageLen = iMessageLen + strlen(oTemp -> sCatalogName);
		sMessage[iMessageLen] = TYPE_IS_CATALOG_RESPONSE;
		iMessageLen++;
		oTemp = oTemp -> ptrNext;
	}
	sMessage[iMessageLen] = '\0';
	sMessage[iMessageLen + 1] = '\0';
	iMessageLen += 2;

	// Broadcast to all sockets
	server_SendServerMessage(iSocket, server_CreateMessage(TYPE_IS_CATALOG_RESPONSE, sMessage, iMessageLen));

	// Free allocated space
	free(sMessage);

	return 0;
}


int catalog_BroadcastSelectedCatalog() {
	int i;
	int iCount = catalog_GetCatalogCount();
	int iMessageLen;
	char *sMessage = NULL;
	struct CatalogInfo *oTemp = catalog_GetCatalogList();
	struct UserInfo *oUser = user_GetUserList();

	for (i = 0; i < iCount; i++) {
		if (oTemp -> bIsSelected == 1) {
			i = strlen(oTemp -> sCatalogName);
			sMessage = malloc((i + 2) * sizeof(char)+2);
			sMessage[0] = (uint8_t)(i / 256);
			sMessage[1] = (uint8_t)i;
			strcpy(sMessage + 2, oTemp -> sCatalogName);
			iMessageLen = i + 2;
			break;
		}
		oTemp = oTemp -> ptrNext;
	}
	if (sMessage != NULL) {
		iCount = user_GetUserCount();
		for (i = 0; i < iCount; i++) {
			if (oUser -> iUserID > 0) {
				// Send
				server_SendServerMessage(oUser -> iSocket, server_CreateMessage(TYPE_IS_CATALOG_CHANGE, sMessage, iMessageLen));
			}
			oUser = oUser -> ptrNext;
		}
		// Free allocated space
		free(sMessage);
		return 0;
	} else {
		return -1;
	}
}
